﻿#include "ssReadini.h"


namespace StarSeeker
{

ssReadini::ssReadini()
{
}

bool ssReadini::Open(const char* path)
{
	m_cfg.clear();
	m_file.SetPath(path);
	if (m_file.OpenFile(false))
	{
		std::string t;
		std::string k;
		std::string v;
		std::string tmp;
		while (m_file.GetLine(0, 0))
		{
			char* buf = m_file.GetBuffer().Buf();
			ulint size = ::strlen(m_file.GetBuffer().Buf());
			if (buf[0]==';' || buf[0] == '\n' || buf[0] == '\r')
			{
				continue;
			}
			else if (buf[0]=='[') //找节
			{
				ulint end = 0;
				for (ulint i=0; i<size; ++i)
				{
					if (buf[i]==']')
					{
						end = i;
						break;
					}
				}
				if (end > 0)
				{
					t.assign(buf + 1, end - 1);
				}
			}
			else
			{
				//找=
				ulint eq = 0;
				for (ulint i=0; i<size; ++i)
				{
					if (buf[i]=='=')
					{
						eq = i;
						break;
					}
				}
				if (eq > 0)
				{
					//键
					k.assign(buf, eq);
					//值
					ulint vend = 0;
					for (ulint i=eq; i<size; ++i)
					{
						if (buf[i]=='\n' || buf[i]=='\r')
						{
							vend = i;
							break;
						}
					}
					if (vend==0 && size>eq)
					{
						vend = size;
					}
					if (vend > eq)
					{
						v.assign(buf + eq + 1, vend - eq - 1);
						PushString(t.c_str(), k.c_str(), v.c_str());
					}
				}
			}
		}
		m_file.CloseFile();
		return true;
	}
	return false;
}

bool ssReadini::PushString(const char* node, const char* key, const char* value)
{
	std::map<std::string, KV_T>::iterator itrNode = m_cfg.find(node);
	if (itrNode == m_cfg.end())
	{
		KV_T kv;
		std::pair<KV_T::iterator, bool> pKV = kv.insert(std::pair<std::string,std::string>(key, value));
		if (pKV.second)
		{
			std::pair<std::map<std::string, KV_T>::iterator, bool> pNode = m_cfg.insert(std::pair<std::string, KV_T>(node, kv));
			if (pNode.second)
			{
				pNode.first->second.insert(std::pair<std::string,std::string>(key, value));
				return true;
			}
		}
	}
	else
	{
		itrNode->second.insert(std::pair<std::string,std::string>(key, value));
		return true;
	}
	return false;
}

std::string& ssReadini::GetString(const char* node, const char* key, const char* defValue)
{
	std::map<std::string, KV_T>::iterator itrNode = m_cfg.find(node);
	if (itrNode != m_cfg.end())
	{
		KV_T::iterator itr = itrNode->second.find(key);
		if (itr != itrNode->second.end())
		{
			return itr->second;
		}
	}
	m_error = defValue;
	return m_error;
}

int ssReadini::GetInt32(const char* node, const char* key, int defValue)
{
	std::string* str = &GetString(node, key, " ");
	if (str==&m_error)
	{
		return defValue;
	}
	return ::atoi(str->c_str());
}

long long ssReadini::GetInt64(const char* node, const char* key, long long defValue)
{
	std::string* str = &GetString(node, key, " ");
	if (str == &m_error)
	{
		return defValue;
	}
	return ::atoll(str->c_str());
}

}
